<template>
  <div class="app">
    <component :is="currentView" />
  </div>
</template>

<script setup>
import { ref, provide, onMounted } from 'vue';
import HomePage from './components/HomePage.vue';
import MatchingPage from './components/MatchingPage.vue';
import BackpackPage from './components/BackpackPage.vue';
import MyBox from './components/MyBox.vue';
import GetPokemon from './components/GetPokemon.vue';
import pokemon_enService from '@/api/services/pokemon_enService';
import movesService from '@/api/services/movesService';
import { typeMap } from '@/api/constants';

// Helper function to calculate Pokémon stats
const calculateStat = (base, level, iv = 15, ev = 0, isHp = false) => {
  const basePart = Math.floor(((2 * base + iv + Math.floor(ev / 4)) * level) / 100);
  return isHp ? basePart + level + 10 : basePart + 5;
};

// Define the available pages
const pages = {
  home: HomePage,
  matching: MatchingPage,
  backpack: BackpackPage,
  myBox: MyBox,
  getPokemon: GetPokemon
};

// Set the initial page
const currentView = ref(pages.home);

// Reactive Pokémon data
const myPokemon = ref([]);
const boxPokemon = ref([]);

// Items inventory
const items = ref({
  pokeBall: 10,
  potion: 5
});

// Navigation function to change pages
const navigate = (page) => {
  console.log(`Navigating to: ${page}`);
  if (pages[page]) {
    currentView.value = pages[page];
  } else {
    console.error(`Page ${page} not found in pages object`);
  }
};

// Function to fetch Pokémon data from local API
const fetchPokemonData = async () => {
  const myPokemonIds = [4, 7, 1]; // Charmander, Squirtle, Bulbasaur
  const myPokemonLevels = [5, 5, 5];
  const boxPokemonIds = [25]; // Pikachu
  const boxPokemonLevels = [5];

  try {
    // Fetch myPokemon data
    const myPokemonData = await Promise.all(
        myPokemonIds.map(async (id, index) => {
          const pokemonResponse = await pokemon_enService.getPokemonById(id);
          const types = pokemonResponse.types
              .map(t => typeMap[t.type.name.toLowerCase()] || t.type.name)
              .join('/');
          const stats = pokemonResponse.stats.reduce((acc, stat) => {
            acc[stat.stat.name] = stat.base_stat;
            return acc;
          }, {});
          const level = myPokemonLevels[index];

          // Use the first 4 moves from the Pokémon's moves array
          const moves = pokemonResponse.moves.slice(0, 4).map(move => ({
            id: move.move.url.split('/').slice(-2, -1)[0] // Extract move ID from URL
          }));

          const moveDetails = await Promise.all(
              moves.map(async (move) => {
                try {
                  const moveResponse = await movesService.getMoveById(move.id);
                  return {
                    name: moveResponse.name_zh,
                    type: typeMap[moveResponse.type.toLowerCase()] || moveResponse.type,
                    pp: 25
                  };
                } catch (error) {
                  return { name: '撞击', type: '一般', pp: 35 };
                }
              })
          );

          return {
            id: pokemonResponse.id,
            name: pokemonResponse.name,
            type: types,
            level,
            hp: calculateStat(stats.hp || 50, level, 15, 0, true),
            maxHp: calculateStat(stats.hp || 50, level, 15, 0, true),
            attack: calculateStat(stats.attack || 50, level),
            defense: calculateStat(stats.defense || 50, level),
            specialAttack: calculateStat(stats['special-attack'] || 50, level),
            specialDefense: calculateStat(stats['special-defense'] || 50, level),
            speed: calculateStat(stats.speed || 50, level),
            moves: moveDetails.length > 0 ? moveDetails : [{ name: '撞击', type: '一般', pp: 35 }]
          };
        })
    );
    myPokemon.value = myPokemonData;

    // Fetch boxPokemon data
    const boxPokemonData = await Promise.all(
        boxPokemonIds.map(async (id, index) => {
          const pokemonResponse = await pokemon_enService.getPokemonById(id);
          const types = pokemonResponse.types
              .map(t => typeMap[t.type.name.toLowerCase()] || t.type.name)
              .join('/');
          const stats = pokemonResponse.stats.reduce((acc, stat) => {
            acc[stat.stat.name] = stat.base_stat;
            return acc;
          }, {});
          const level = boxPokemonLevels[index];

          const moves = pokemonResponse.moves.slice(0, 4).map(move => ({
            id: move.move.url.split('/').slice(-2, -1)[0]
          }));

          const moveDetails = await Promise.all(
              moves.map(async (move) => {
                try {
                  const moveResponse = await movesService.getMoveById(move.id);
                  return {
                    name: moveResponse.name_zh,
                    type: typeMap[moveResponse.type.toLowerCase()] || moveResponse.type,
                    pp: 25
                  };
                } catch (error) {
                  return { name: '撞击', type: '一般', pp: 35 };
                }
              })
          );

          return {
            id: pokemonResponse.id,
            name: pokemonResponse.name,
            type: types,
            level,
            hp: calculateStat(stats.hp || 50, level, 15, 0, true),
            maxHp: calculateStat(stats.hp || 50, level, 15, 0, true),
            attack: calculateStat(stats.attack || 50, level),
            defense: calculateStat(stats.defense || 50, level),
            specialAttack: calculateStat(stats['special-attack'] || 50, level),
            specialDefense: calculateStat(stats['special-defense'] || 50, level),
            speed: calculateStat(stats.speed || 50, level),
            moves: moveDetails.length > 0 ? moveDetails : [{ name: '撞击', type: '一般', pp: 35 }]
          };
        })
    );
    boxPokemon.value = boxPokemonData;
  } catch (error) {
    console.error('Error fetching Pokémon data:', error);
    myPokemon.value = [];
    boxPokemon.value = [];
  }
};

// Fetch data when component is mounted
onMounted(() => {
  fetchPokemonData();
});

// Make navigation and data available to all components
provide('navigate', navigate);
provide('myPokemon', myPokemon);
provide('boxPokemon', boxPokemon);
provide('items', items);
</script>

<style>
* {
  margin: 0;
  padding: 0;
  box-sizing: border-box;
  font-family: 'Arial', sans-serif;
}

.app {
  min-height: 100vh;
  background: linear-gradient(to bottom, #3498db, #2980b9);
}

button {
  cursor: pointer;
  border: none;
  border-radius: 4px;
  padding: 10px 16px;
  font-weight: bold;
  transition: background-color 0.3s, transform 0.1s;
}

button:hover {
  transform: translateY(-2px);
}

button:active {
  transform: translateY(0);
}
</style>